
from direct.gui.DirectGui import DirectLabel
from Cube.gui.QOptionMenu import QOptionMenu
from Cube.map import QMemberType
from Cube.gui.DirectGUIPropertiesAccess import AlignText

class UpdateProcess:
    def __init__(self, typeString = None):
        if typeString is not None:
            global MemberTypeStringMap
            MemberTypeStringMap.update(typeString)
        self.OptionCallback = DefaultOptionCallback

    def Update(self, MemberData):
        # MemberData: Cube.map.QMemberList.QMemberListMgr
        myMemberID = MemberData.MyMemberIDGet()
        memberList = MemberData.MemberListGet()
        memberListControlItemList = self.MemberListControlItemList
        for (i, (memberEntry, guiItem)) in enumerate(zip(memberList,memberListControlItemList)):
            if memberEntry.MemberID == myMemberID:
                self._LabelUpdate(guiItem, memberEntry, i)
            else:
                if self.connectType == "server":
                    self._OptionUpdate(guiItem, memberEntry, i)
                else:
                    self._LabelUpdate(guiItem, memberEntry, i)

    def _LabelUpdate(self, guiItem, memberEntry, i):
        memberName = LabelItemProcess(memberEntry)
        if isinstance(guiItem, DirectLabel):
            if guiItem["text"] != memberName:
                guiItem["text"] = memberName
        else:
            labelObj = self._Option2Label(guiItem, memberName)
            self.MemberListControlItemList[i] = labelObj

    def _OptionUpdate(self, guiItem, memberEntry, i):
        optionItems, selectedID = OptionItemProcess(memberEntry)
        if isinstance(guiItem, QOptionMenu):
            if guiItem["items"] != optionItems:
                guiItem["items"] = optionItems
            guiItem.set(selectedID, fCommand = False)
        else:
            optionObj = self._Label2Option(guiItem, optionItems, memberEntry.MemberID)
            optionObj.set(selectedID, fCommand = False)
            self.MemberListControlItemList[i] = optionObj

    def _Label2Option(self, labelObj, items, memberID):
        self.paramIn_optionMember["pos"] = labelObj.getPos()
        self.paramIn_optionMember["frameSize"] = labelObj["frameSize"]
        self.paramIn_optionMember["items"] = items
        self.paramIn_optionMember["command"] = self.OptionCallback
        self.paramIn_optionMember["extraArgs"] = [memberID]
        optionObj = QOptionMenu(**self.paramIn_optionMember)
        AlignText(optionObj, "left")
        labelObj.destroy() # remove label
        return optionObj

    def _Option2Label(self, optionObj, labelString):
        self.paramIn_labelMember["pos"] = optionObj.getPos()
        self.paramIn_labelMember["frameSize"] = optionObj["frameSize"]
        self.paramIn_labelMember["text"] = labelString
        labelObj = DirectLabel(**self.paramIn_labelMember)
        AlignText(labelObj, "left")
        optionObj.destroy() # remove option
        return labelObj

    def OptionCallbackSet(self, fn):
        self.OptionCallback = fn

# ----
MemberTypeStringMap = {QMemberType.HUMAN:QMemberType.HUMAN,
                       QMemberType.COMPUTER:QMemberType.COMPUTER,
                       QMemberType.OPEN:QMemberType.OPEN,
                       QMemberType.CLOSE:QMemberType.CLOSE
                       }

def LabelItemProcess(memberEntry):
    currType = memberEntry.CurrentMemberType
    if currType == QMemberType.HUMAN:
        ret = memberEntry.MemberName
    else:
        ret = MemberTypeStringMap[currType]
    return ret

def OptionItemProcess(memberEntry):
    currType = memberEntry.CurrentMemberType
    # type string mapping
    ret = [ MemberTypeStringMap[typeString]
            for typeString in memberEntry.OptionMemberType ]
    StringHUMAN = MemberTypeStringMap[QMemberType.HUMAN]
    if currType == QMemberType.HUMAN:
        selectedID = ret.index(StringHUMAN)
        ret[selectedID] = memberEntry.MemberName
    elif (StringHUMAN in ret):
        del ret[ret.index(StringHUMAN)]
        selectedID = ret.index(MemberTypeStringMap[currType])
    return ret, selectedID

# ----
def DefaultOptionCallback(arg, memberID):
    print "DefaultOptionCallback", arg, memberID
